Repository navigation
API: coarse-grained checker queries for whole-program extraction tools - #65351
Open
WinterYukky (WinterYukky) wants to merge 3 commits into
Open
WinterYukky (WinterYukky) wants to merge 3 commits into
WinterYukky (WinterYukky) wants to merge 3 commits into
Conversation
Contributor
There was a problem hiding this comment.
🟡 Changes recommended
The implementation drops valid declarationless members even without a filter, with additional unresolved errors in member classification, visibility, pattern handling, and optional-field typing.
6 open issues
Preserve declarationless symbols in member results · New Allow undefined for optional filter fields · New Distinguish empty exclusion patterns from omitted patterns · New Classify accessor visibility independent of declaration order · New Use consistent method classification for synthesized union symbols · New Recognize auto-accessors in member kind filters · New
What changed in this PR
Adds coarse-grained checker queries for whole-program extraction tools, addressing #65051 by reducing per-member API round trips.
Changes:
- Adds bulk symbol documentation and filtered member queries to the Go API.
- Exposes both methods through async, sync, and generator clients, using the existing object registry.
- Adds predicate, differential, identity, and client-parity tests.
| File | Description |
|---|---|
tsc/internal/api/session.go |
Implements request handlers, member filtering, and metadata collection. |
tsc/internal/api/session_members_test.go |
Tests filters and bulk documentation equivalence. |
tsc/internal/api/session_members_differential_test.go |
Compares member results with fine-grained queries. |
tsc/internal/api/proto.go |
Defines protocol methods, filters, and response types. |
packages/typescript/test/sync/api.test.ts |
Tests synchronous queries and object identity. |
packages/typescript/test/sync/api-generators.test.ts |
Adds generator-batching parity checks. |
packages/typescript/test/async/api.test.ts |
Tests asynchronous queries and object identity. |
packages/typescript/src/api/sync/api.ts |
Adds generated sync and generator interfaces. |
packages/typescript/src/api/proto.generated.ts |
Adds generated protocol declarations. |
packages/typescript/src/api/async/api.ts |
Implements public async methods and result conversion. |
Review effort: Balanced
…cker queries for traversal tools Tools that walk a whole program (binding generators, documentation generators, API extractors) ask the checker, for every member of every type, for its documentation and its type, and skip most members after looking at them. Over the synchronous API that is several round trips per member, and the server materializes a type for members the caller then discards. getSymbolDocumentations returns the JSDoc tags and documentation comment of many symbols in one request, element for element equal to getJsDocTags and getDocumentationComment. getMembersOfType returns the properties of a type that pass a filter, each with its documentation, the symbol of the type declaring it and, on request, its declared type. The filter is a set of neutral predicates (visibility, member kind, excluded JSDoc tags, an excluded name pattern, which declaring types to take members from) that the caller combines to describe the members it will render; a tool's own policy stays in the tool. Members come back in getPropertiesOfType order with the same symbol and type handles. The Go tests include a differential fixture: a class hierarchy with overrides, overloads, accessors, every visibility including an ECMAScript private name, a parameter property and excluded members, checked member by member against what the fine-grained path (getPropertiesOfType + getTypeOfSymbolAtLocation + getJsDocTags + getDocumentationComment) reports. The client tests cover the two methods through the API and in the generator batching parity suite. Refs: microsoft#65051
remote-swe
Bot
force-pushed
the
api/coarse-checker-queries
branch
from
November 6, 2026 02:28
bad7efe to
3fcd4c6
Compare
…er than their first declaration
Review of the first version found six gaps, all in how a member's metadata
was derived from its first declaration:
- Members without a declaration (tuple elements, a tuple's `length`) were
dropped even with no filter, so the result diverged from
getPropertiesOfType. They are kept, classified from their symbol flags,
have no owner, and their declared type comes from getTypeOfSymbol, which
needs no location; the declared type of every member is now obtained that
way.
- Visibility is read with GetDeclarationModifierFlagsFromSymbol, so a
getter/setter pair is classified by the getter whatever the declaration
order, and a synthetic union or intersection member by its constituents.
ECMAScript private names still count as private.
- isMethod is derived from the same classification as the `method` kind, so
the synthetic member of `{ m(): number } | { m(): string }`, which carries
no method flag, is a method and gets no declared type.
- Auto-accessors (`accessor x = 0`) are accessors, like explicit getters and
setters.
- excludeNamePattern distinguishes absent from empty: a pattern that is
passed is always compiled, and the empty pattern matches every member.
- MemberFilterInput accepts an explicit `undefined` for every optional field,
nested ones included, under exactOptionalPropertyTypes.
Each gap has a test that failed before the change.
Refs: microsoft#65351
…(modernize linter)
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.


Fixes #65051
Summary
Tools that walk a whole program through the API ask the checker, for every type and every member, for its properties, declared type, declaring type and JSDoc as separate round trips, so their running time is bounded by the message count rather than by checker work. On aws-cdk-lib, jsii issues about 700k requests while the server spends about 6 s computing types, and most of the members it asks about are inspected and then discarded. This PR adds two methods that return the same information in one round trip.
getMembersOfTypetakes a filter so that no type is materialised for a member the caller would drop. The handles returned are the same ones the existing methods return, and jsii's.jsiioutput is byte-identical between the two paths.What changes
On the Go side,
proto.gogains the two methods and theMemberFilter/TypeMembertypes, andsession.gogains their handlers. Filter predicates are evaluated cheapest first, and an invalidexcludeNamePatternis reported as a client error.owneris returned as aSymbolResponse, so on the client it is the sameSymbolobject the caller already holds.On the client side,
async/api.tsgains the two methods;sync/api.tsandproto.generated.tsare regenerated. Returned symbols and types go through the registry, so they are identical to the objects returned by the existing methods. No existing method or type changes.Filter options
visibilitykindsproperty,accessor,method,parameterProperty)excludeJsDocTagsexcludeNamePatternincludeInheritedFrom{}: own members only;{ declaringTypes }: members declared by the given typesincludeDeclaredTypeWith no filter,
getMembersOfTypereturns the same symbols in the same order asgetPropertiesOfType.Tests
Go unit tests cover predicate combinations,
kindsclassification, the empty filter againstgetPropertiesOfType, invalid patterns, andgetSymbolDocumentationsagainst the individual methods element by element. A differential test runs the existing fine-grained queries andgetMembersOfTypeover the same program (inheritance with overrides, overloads, accessors, all three visibilities plus ECMAScript private names, members excluded by JSDoc tag and by name pattern) and compares handles, declared types, documentation and ordering for every member. Client-side API tests are added as well.hereby test,test:api,lintandcheck:formatpass.Numbers
Same fork build, c7i.4xlarge, aws-cdk-lib benchmark, median of 3 runs,
.jsiioutput byte-identical between the two paths:getSymbolDocumentations+getMembersOfTypeA current aws-cdk-lib checkout built from source (2 runs): 43.2 / 43.1 s → 37.8 / 38.2 s, requests 783k → 340k, bytes sent 168 MB → 65 MB, server time unchanged.